package com.yxdj.order.service.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yxdj.common.core.constant.SecurityConstants;
import com.yxdj.common.core.domain.R;
import com.yxdj.common.core.exception.ServiceException;
import com.yxdj.common.rabbit.constant.MqConst;
import com.yxdj.common.security.utils.SecurityUtils;
import com.yxdj.order.api.domain.OrderInfo;
import com.yxdj.order.domain.dto.AppointmentDto;
import com.yxdj.order.domain.dto.OrderInfoDto;
import com.yxdj.order.domain.vo.AppointmentSubmitVo;
import com.yxdj.order.mapper.OrderInfoMapper;
import com.yxdj.order.service.OrderInfoService;
import com.yxdj.user.api.RemoteAddressService;
import com.yxdj.user.api.RemoteEngineerService;
import com.yxdj.user.api.RemoteManageUserService;
import com.yxdj.user.api.domain.Address;
import com.yxdj.user.api.domain.Engineer;
import com.yxdj.user.api.domain.User;
import org.redisson.api.RBlockingDeque;
import org.redisson.api.RDelayedQueue;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @author 韩总
 * @description 针对表【order_info】的数据库操作Service实现
 * @createDate 2025-03-25 16:50:47
 */
@Service
public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo>
        implements OrderInfoService {

    @Autowired
    private RemoteManageUserService remoteManageUserService;

    @Autowired
    private RemoteEngineerService remoteEngineerService;

    @Autowired
    private RemoteAddressService remoteAddressService;

    @Autowired
    private RedissonClient redissonClient;

    @Override
    public OrderInfo getOrderInfoById(Long id) {
        OrderInfo orderInfo = baseMapper.selectById(id);
        R<User> user = remoteManageUserService.getUserById(orderInfo.getUserId(), SecurityConstants.INNER);
        if (R.FAIL == user.getCode()) {
            throw new ServiceException(user.getMsg());
        }
        orderInfo.setUserNickName(user.getData().getNickname());
        if (orderInfo.getEngineerId() != null) {
            R<Engineer> engineer = remoteEngineerService.getEngineerById(orderInfo.getEngineerId(), SecurityConstants.INNER);
            if (R.FAIL == engineer.getCode()) {
                throw new ServiceException(engineer.getMsg());
            }
            orderInfo.setEngineerName(engineer.getData().getName());
        }

        return orderInfo;
    }

    @Override
    public AppointmentSubmitVo toAppointmentPage(AppointmentDto appointmentDto) {
        //创建AppointmentSubmitVo对象
        AppointmentSubmitVo appointmentSubmitVo = new AppointmentSubmitVo();
        //服务项目名
        appointmentSubmitVo.setServiceOptionName(appointmentDto.getServiceOptionName());
        //设置上门费用
        appointmentSubmitVo.setServiceFee(0.0);
        //设置服务详情id
        appointmentSubmitVo.setServiceDetailId(appointmentDto.getServiceDetailId());
        //获取用户id
        Long userId = SecurityUtils.getUserId();
//        Long userId = 1L;
        if (userId != null) {
            //远程调用用户微服务获取用户地址
            R<List<Address>> userAddressByUserId = remoteAddressService.getUserAddressByUserId(userId, SecurityConstants.INNER);
            if(R.FAIL == userAddressByUserId.getCode()){
                throw new ServiceException(userAddressByUserId.getMsg());
            }
            appointmentSubmitVo.setAddressList(userAddressByUserId.getData());
        }
        return appointmentSubmitVo;
    }

    @Override
    public Long saveOrder(OrderInfoDto orderInfoDto) {
        //远程调用用户微服务获取上门地址
        R<Address> addressById = remoteAddressService.getAddressById(orderInfoDto.getAddressId(), SecurityConstants.INNER);
        if(R.FAIL == addressById.getCode()){
            throw new ServiceException(addressById.getMsg());
        }
        Address address = addressById.getData();
        //创建OrderInfo对象
        OrderInfo orderInfo = new OrderInfo();
        //设置用户id
        orderInfo.setUserId(address.getUserId());
        //设置服务详情id
        orderInfo.setServiceDetailId(orderInfoDto.getServiceDetailId());
        //设置服务项目名
        orderInfo.setServiceOptionName(orderInfoDto.getServiceOptionName());
        //设置订单号
        orderInfo.setOrderNumber(String.valueOf(System.currentTimeMillis()+address.getUserId()));
        //设置预约时间
        orderInfo.setAppointmentTime(orderInfoDto.getAppointmentTime());
        //设置服务地址
        orderInfo.setServiceAddress(address.getProvinceName()+address.getCityName()+address.getDistrictName()+address.getDetailAddress()+address.getBuildingOrHouseNumber());
        //设置联系人姓名
        orderInfo.setContactName(address.getContactName());
        //设置联系人电话
        orderInfo.setContactPhone(address.getPhoneNumber());
        //设置上门费用
        orderInfo.setServiceFee(orderInfoDto.getServiceFee());
        //设置订单状态
        orderInfo.setOrderStatus(0);
        //保存订单
        baseMapper.insert(orderInfo);

        //延迟关单
        sendDelayMessage(orderInfo.getId());
        return orderInfo.getId();
    }

    @Override
    public void cancelOrder(long orderId) {
        OrderInfo orderInfo = baseMapper.selectById(orderId);
        if(null != orderInfo && orderInfo.getOrderStatus().intValue() == 0) {
            orderInfo.setOrderStatus(5);
            orderInfo.setUpdateTime(new Date());
            orderInfo.setCancelReason("匹配不到工程师自动取消");
            baseMapper.updateById(orderInfo);
        }
    }

    //发送延迟队列
    private void sendDelayMessage(Long orderId) {
        try {
            //1 创建阻塞队列
            RBlockingDeque<Object> blockingDeque =
                    redissonClient.getBlockingDeque(MqConst.QUEUE_CANCEL_ORDER);
            //2 创建延迟队列 1
            RDelayedQueue<Object> delayedQueue = redissonClient.getDelayedQueue(blockingDeque);

            //3 向队列放消息，设置延迟时间
            delayedQueue.offer(orderId.toString(),30, TimeUnit.MINUTES);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}




